﻿// windownative.cpp
#include "windownative.h"
#include <QGuiApplication>
#include <QScreen>
#include <QDebug>
// #include <QtWinExtras>

// 兼容性定义
#ifndef DWMWA_USE_IMMERSIVE_DARK_MODE
#define DWMWA_USE_IMMERSIVE_DARK_MODE 20
#endif

#include <windows.h>
#include <dwmapi.h>
#include <windowsx.h>

#pragma comment(lib, "dwmapi.lib")
#pragma comment(lib, "user32.lib")

WindowsNative::WindowsNative(QObject *parent) : QObject(parent)
{
}

QWindow *WindowsNative::findWindowHandle(QWindow *window)
{
    while (window && !window->handle()) {
        window = window->parent();
    }
    return window;
}

void WindowsNative::setWindowFrame(QWindow *window)
{
    QWindow *win = findWindowHandle(window);
    if (!win) return;

    HWND hwnd = reinterpret_cast<HWND>(win->winId());

    // 动态加载 dwmapi 函数
    HMODULE dwmapiLib = LoadLibraryA("dwmapi.dll");
    if (dwmapiLib) {
        auto pDwmExtendFrameIntoClientArea = reinterpret_cast<DwmExtendFrameIntoClientAreaPtr>(
            GetProcAddress(dwmapiLib, "DwmExtendFrameIntoClientArea"));
        auto pDwmSetWindowAttribute = reinterpret_cast<DwmSetWindowAttributePtr>(
            GetProcAddress(dwmapiLib, "DwmSetWindowAttribute"));

        if (pDwmExtendFrameIntoClientArea) {
            const MARGINS shadow = { 1, 1, 1, 1 };
            pDwmExtendFrameIntoClientArea(hwnd, &shadow);
        }

        if (pDwmSetWindowAttribute) {
            DWORD policy = DWMNCRP_ENABLED;
            pDwmSetWindowAttribute(hwnd, DWMWA_NCRENDERING_POLICY, &policy, sizeof(policy));

            BOOL extendIntoTitleBar = TRUE;
            pDwmSetWindowAttribute(hwnd, DWMWA_ALLOW_NCPAINT, &extendIntoTitleBar, sizeof(extendIntoTitleBar));
        }

        FreeLibrary(dwmapiLib);
    }

    // 设置窗口样式
    SetWindowLongPtr(hwnd, GWL_STYLE,
                     GetWindowLongPtr(hwnd, GWL_STYLE) |
                         WS_THICKFRAME | WS_CAPTION | WS_MAXIMIZEBOX | WS_MINIMIZEBOX);
}

void WindowsNative::setWindowTitleBar(QWindow *window, int titleBarHeight)
{
    QWindow *win = findWindowHandle(window);
    if (!win) return;

    HWND hwnd = reinterpret_cast<HWND>(win->winId());

    // 动态加载 dwmapi 函数
    HMODULE dwmapiLib = LoadLibraryA("dwmapi.dll");
    if (dwmapiLib) {
        auto pDwmSetWindowAttribute = reinterpret_cast<DwmSetWindowAttributePtr>(
            GetProcAddress(dwmapiLib, "DwmSetWindowAttribute"));

        if (pDwmSetWindowAttribute) {
            BOOL useImmersiveDarkMode = TRUE;
            pDwmSetWindowAttribute(hwnd, DWMWA_USE_IMMERSIVE_DARK_MODE,
                                   &useImmersiveDarkMode, sizeof(useImmersiveDarkMode));
        }

        FreeLibrary(dwmapiLib);
    }

    // 刷新窗口
    SetWindowPos(hwnd, nullptr, 0, 0, 0, 0,
                 SWP_FRAMECHANGED | SWP_NOACTIVATE | SWP_NOMOVE | SWP_NOSIZE | SWP_NOZORDER);
}

void WindowsNative::startSystemMove(QWindow *window, const QPoint &cursorPos)
{
    QWindow *win = findWindowHandle(window);
    if (!win) return;

    HWND hwnd = reinterpret_cast<HWND>(win->winId());
    ReleaseCapture();
    SendMessage(hwnd, WM_SYSCOMMAND, SC_MOVE | HTCAPTION, 0);
}

void WindowsNative::startSystemResize(QWindow *window, const QPoint &cursorPos, Qt::Edges edges)
{
    QWindow *win = findWindowHandle(window);
    if (!win) return;

    HWND hwnd = reinterpret_cast<HWND>(win->winId());
    ReleaseCapture();

    WPARAM wparam = 0;
    if (edges & Qt::TopEdge) {
        if (edges & Qt::LeftEdge) wparam = HTTOPLEFT;
        else if (edges & Qt::RightEdge) wparam = HTTOPRIGHT;
        else wparam = HTTOP;
    } else if (edges & Qt::BottomEdge) {
        if (edges & Qt::LeftEdge) wparam = HTBOTTOMLEFT;
        else if (edges & Qt::RightEdge) wparam = HTBOTTOMRIGHT;
        else wparam = HTBOTTOM;
    } else if (edges & Qt::LeftEdge) {
        wparam = HTLEFT;
    } else if (edges & Qt::RightEdge) {
        wparam = HTRIGHT;
    }

    SendMessage(hwnd, WM_SYSCOMMAND, SC_SIZE | wparam, 0);
}

void WindowsNative::showSystemMenu(QWindow *window, const QPoint &pos)
{
    QWindow *win = findWindowHandle(window);
    if (!win) return;

    HWND hwnd = reinterpret_cast<HWND>(win->winId());
    HMENU hMenu = GetSystemMenu(hwnd, FALSE);

    if (hMenu) {
        // 更新菜单项状态
        UINT uFlags = MF_BYCOMMAND;
        if (IsZoomed(hwnd)) {
            uFlags |= MF_GRAYED;
        }
        EnableMenuItem(hMenu, SC_RESTORE, uFlags);
        EnableMenuItem(hMenu, SC_MOVE, uFlags);
        EnableMenuItem(hMenu, SC_SIZE, uFlags);
        EnableMenuItem(hMenu, SC_MINIMIZE, uFlags);
        EnableMenuItem(hMenu, SC_MAXIMIZE, uFlags);

        // 显示菜单
        int cmd = TrackPopupMenu(hMenu, TPM_LEFTBUTTON | TPM_RETURNCMD,
                                 pos.x(), pos.y(), 0, hwnd, nullptr);
        if (cmd) {
            SendMessage(hwnd, WM_SYSCOMMAND, cmd, 0);
        }
    }
}

void WindowsNative::maximizeWindow(QWindow *window)
{
    QWindow *win = findWindowHandle(window);
    if (!win) return;

    HWND hwnd = reinterpret_cast<HWND>(win->winId());
    ShowWindow(hwnd, SW_MAXIMIZE);
}

void WindowsNative::minimizeWindow(QWindow *window)
{
    QWindow *win = findWindowHandle(window);
    if (!win) return;

    HWND hwnd = reinterpret_cast<HWND>(win->winId());
    ShowWindow(hwnd, SW_MINIMIZE);
}

void WindowsNative::restoreWindow(QWindow *window)
{
    QWindow *win = findWindowHandle(window);
    if (!win) return;

    HWND hwnd = reinterpret_cast<HWND>(win->winId());
    ShowWindow(hwnd, SW_RESTORE);
}

void WindowsNative::closeWindow(QWindow *window)
{
    QWindow *win = findWindowHandle(window);
    if (!win) return;

    HWND hwnd = reinterpret_cast<HWND>(win->winId());
    SendMessage(hwnd, WM_CLOSE, 0, 0);
}

bool WindowsNative::isWindowMaximized(QWindow *window)
{
    QWindow *win = findWindowHandle(window);
    if (!win) return false;

    HWND hwnd = reinterpret_cast<HWND>(win->winId());
    return IsZoomed(hwnd);
}

bool WindowsNative::isWindowFullScreen(QWindow *window)
{
    QWindow *win = findWindowHandle(window);
    if (!win) return false;

    return win->windowState() == Qt::WindowFullScreen;
}
